﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.Drawing;
using System.IO;
using System.Xml;

namespace Core
{
    /// <summary>
    /// Класс управления рейтингом
    /// Реализует расчёт рейтинга, управление файлами и экспорт в HTML
    /// </summary>
    public static class RetingManagement
    {
        public static SchoolClass PreviewData = null;

        /// <summary>
        /// Расчёт рейтинга по классу
        /// </summary>
        /// <param name="Class"></param>
        public static void CalcResult(ref Pupil[] Class)
        {
            try
            {
                #region Расчёт Бонусов по всем предметам
                for (int cstudy = 0; cstudy < Class[0].StudyBall.Length; cstudy++)
                {
                    //sort all people in Class
                    Pupil temp = null;
                    bool changed = true;
                    while (changed)
                    {
                        changed = false;
                        for (int i = 0; i < Class.Length - 1; i++)
                        {
                            if (Class[i].StudyBall[cstudy] < Class[i + 1].StudyBall[cstudy])
                            {
                                temp = Class[i];
                                Class[i] = Class[i + 1];
                                Class[i + 1] = temp;
                                changed = true;
                            }
                        }
                    }
                    //CalcResult with Curent Study
                    Group[] pgroup = new Group[1] { new Group() };
                    pgroup[0].Ball = Class[0].StudyBall[cstudy];
                    int cgroup = 0;
                    int cball = Class.Length;
                    //      
                    for (int cpupil = 0; cpupil < Class.Length; cpupil++)
                    {
                        if (Class[cpupil].StudyBall[cstudy] != pgroup[cgroup].Ball)
                        {
                            Array.Resize(ref pgroup, pgroup.Length + 1);
                            cgroup++;
                            pgroup[cgroup] = new Group();
                            pgroup[cgroup].Ball = Class[cpupil].StudyBall[cstudy];
                        }
                        pgroup[cgroup].AddToGroup(Class[cpupil]);
                        pgroup[cgroup].Summ += cball;
                        cball--;
                    }
                    int position = 0;
                    for (int j = 0; j < pgroup.Length; j++)
                    {
                        pgroup[j].CalcGroup(cstudy, j + 1);
                        for (int i = 0; i < pgroup[j].PupilGroup.Length; i++)
                        {
                            Class[position] = pgroup[j].PupilGroup[i];
                            position++;
                        }
                    }
                }
                #endregion
                #region Расчёт Бонуса Рейтинга Класса
                for (int i = 0; i < Class.Length; i++)
                {
                    for (int j = 0; j < Class[0].StudyBall.Length; j++)
                        Class[i].ClassBonus = Class[i].ClassBonus + Class[i].PupilResult[j].Bonus;
                }
                #endregion
                #region Сортировка Учеников по Бонусу
                Pupil Ptemp = null;
                bool Pchanged = true;
                while (Pchanged)
                {
                    Pchanged = false;
                    for (int i = 0; i < Class.Length - 1; i++)
                    {
                        if (Class[i].ClassBonus < Class[i + 1].ClassBonus)
                        {
                            Ptemp = Class[i];
                            Class[i] = Class[i + 1];
                            Class[i + 1] = Ptemp;
                            Pchanged = true;
                        }
                    }
                }
                #endregion
                #region Установка мест рейтинга по классу
                Group[] Cgroup = new Group[1] { new Group() };
                Cgroup[0].Ball = Class[0].ClassBonus;
                int group = 0;
                int Cball = Class.Length;
                //
                for (int cpupil = 0; cpupil < Class.Length; cpupil++)
                {
                    if (Class[cpupil].ClassBonus != Cgroup[group].Ball)
                    {
                        Array.Resize(ref Cgroup, Cgroup.Length + 1);
                        group++;
                        Cgroup[group] = new Group();
                        Cgroup[group].Ball = Class[cpupil].ClassBonus;
                    }
                    Cgroup[group].AddToGroup(Class[cpupil]);
                }

                for (group = 0; group < Cgroup.Length; group++)
                {
                    for (int i = 0; i < Cgroup[group].PupilGroup.Length; i++)
                    {
                        Cgroup[group].PupilGroup[i].ClassPlace = group + 1;
                    }
                }
                #endregion
                #region Сортировка Учеников по имени
                Pchanged = true;
                while (Pchanged)
                {
                    Pchanged = false;
                    for (int i = 0; i < Class.Length - 1; i++)
                    {
                        if (String.Compare(Class[i].Name, Class[i + 1].Name) > 0)
                        {
                            Ptemp = Class[i];
                            Class[i] = Class[i + 1];
                            Class[i + 1] = Ptemp;
                            Pchanged = true;
                        }
                    }
                }
                #endregion
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка при подсчёте рейтинга...");
            }
            //Всё на этом страшный метод завершён!
        }

        /// <summary>
        /// Вывод данных рейтинга в таблицу
        /// </summary>
        /// <param name="dgv"></param>
        /// <param name="SchClass"></param>
        public static void FillDataGrid(DataGridView dgv, SchoolClass SchClass)
        {
            if (SchClass == null)
            {
                MessageBox.Show("Отсутствуют данные.", "Ошибка...");
            }
            else
            {
                try
                {
                    DataGridViewCellStyle cellstyle = new DataGridViewCellStyle();

                    dgv.Rows.Clear();
                    dgv.Columns.Clear();
                    dgv.Columns.Add("Family", "Участник");
                    for (int i = 0; i < SchClass.Study.Length; i++)
                    {
                        dgv.Columns.Add("Study" + i.ToString(), SchClass.Study[i]);
                        dgv.Columns[dgv.ColumnCount - 1].Width = 70;
                    }
                    cellstyle.BackColor = Color.Gold;
                    dgv.Columns.Add("Bonus", "Общий балл");
                    dgv.Columns[dgv.ColumnCount - 1].Width = 50;
                    dgv.Columns[dgv.ColumnCount - 1].DefaultCellStyle = cellstyle;

                    cellstyle = new DataGridViewCellStyle();
                    cellstyle.BackColor = Color.Green;
                    dgv.Columns.Add("Place", "Место");
                    dgv.Columns[dgv.ColumnCount - 1].Width = 50;
                    dgv.Columns[dgv.ColumnCount - 1].DefaultCellStyle = cellstyle;
                    for (int i = 0; i < SchClass.group.Length; i++)
                    {
                        dgv.Rows.Add();
                        dgv.Rows[i].Cells[0].Value = SchClass.group[i].Name;
                        for (int j = 0; j < SchClass.group[i].StudyBall.Length; j++)
                        {
                            dgv.Rows[i].Cells[j + 1].Value = SchClass.group[i].StudyBall[j].ToString() +
                                " [" + SchClass.group[i].PupilResult[j].Place.ToString() + "] " +
                                SchClass.group[i].PupilResult[j].Bonus.ToString();
                        }
                        dgv.Rows[i].Cells[dgv.ColumnCount - 2].Value = SchClass.group[i].ClassBonus;
                        dgv.Rows[i].Cells[dgv.ColumnCount - 1].Value = SchClass.group[i].ClassPlace;
                    }
                }
                catch (Exception e)
                {
                    MessageBox.Show(e.Message, "Ошибка...");
                }
            }
        }

        /// <summary>
        /// Вывод данных в файл HTML.
        /// </summary>
        /// <param name="file"></param>
        /// <param name="SchClass"></param>
        public static void FillHTMLpage(string file, SchoolClass SchClass)
        {
            StringBuilder builder = new StringBuilder();
            try
            {
                #region Gen Report
                builder.Append("<HTML>" +
                               "<HEAD><TITLE>" + SchClass.ClassTitle + "</TITLE></HEAD>" +
                               "<BODY>" +
                               "<Font color=green><H2>Автоматический отчёт</H2>" +
                               "<H3>" + SchClass.ClassTitle + "</H3>" +
                               "<H3>Дата: " + DateTime.Now.ToString() + "</H3></Font>" +
                               "<TABLE BORDER=1 cellspacing=0>"
                              );
                //create head of document
                string head = "<TR><TH ROWSPAN=2>Участник</TH>";
                string temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH COLSPAN=3>" + SchClass.Study[i] + "</TH>";
                }
                temp += "<TH ROWSPAN=2>Сумма</TH>" +
                        "<TH ROWSPAN=2>Место</TH>";
                head = head + temp + "</TR>";
                builder.Append(head);
                temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH>Балл</TH><TH>Место</TH><TH>Бонус</TH>";
                }
                temp = "<TR>" + temp + "</TR>";
                builder.Append(temp);
                for (int i = 0; i < SchClass.group.Length; i++)
                {
                    temp = "<TR><TD>" + SchClass.group[i].Name + "</TD>";
                    for (int j = 0; j < SchClass.group[i].PupilResult.Length; j++)
                    {
                        temp += "<TD>" + SchClass.group[i].StudyBall[j].ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Place.ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Bonus + "</TD>";
                    }
                    temp += "<TD>" + SchClass.group[i].ClassBonus.ToString() + "</TD>" +
                           "<TD>" + SchClass.group[i].ClassPlace.ToString() + "</TD>";
                    temp = temp + "</TR>";
                    builder.AppendLine(temp);
                }
                builder.Append("</TABLE>" +
                               "</BR><CODE>code by Jurassik</CODE>" +
                               "</BODY>" +
                               "</HTML>");
                #endregion
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка формирования отчёта.");
            }
            //save report
            try
            {
                if (File.Exists(file))
                    File.Delete(file);
                FileStream stream = new FileStream(file, FileMode.Create);
                StreamWriter writer = new StreamWriter(stream);
                writer.Write(builder.ToString());
                writer.Close();
                stream.Close();
                /*HTMLReport report = new HTMLReport(SchClass.ClassTitle, file);
                report.MdiParent = parent;
                report.Show();*/
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка сохранения файла.");
            }

        }

        /// <summary>
        /// Публикация HTML страницы
        /// </summary>
        /// <param name="file"></param>
        /// <param name="SchClass"></param>
        public static void RenderWebPage(string file, SchoolClass SchClass)
        {
            StringBuilder builder = new StringBuilder();
            try
            {
                #region Gen Report
                builder.Append("<HTML>" +
                               "<HEAD><TITLE>" + SchClass.ClassTitle + "</TITLE></HEAD>" +
                               "<BODY>" +
                               "<Font color=green><H2>Отчёт</H2>" +
                               "<H3>" + SchClass.ClassTitle + "</H3>" +
                               "<H3>Дата: " + DateTime.Now.ToString() + "</H3></Font>" +
                               "<TABLE BORDER=1 cellspacing=0>"
                              );
                //create head of document
                string head = "<TR><TH ROWSPAN=2>Участник</TH>";
                string temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH COLSPAN=3>" + SchClass.Study[i] + "</TH>";
                }
                temp += "<TH ROWSPAN=2>Сумма</TH>" +
                        "<TH ROWSPAN=2>Место</TH>";
                head = head + temp + "</TR>";
                builder.Append(head);
                temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH>Балл</TH><TH>Место</TH><TH>Бонус</TH>";
                }
                temp = "<TR>" + temp + "</TR>";
                builder.Append(temp);
                for (int i = 0; i < SchClass.group.Length; i++)
                {
                    temp = "<TR><TD>" + SchClass.group[i].Name + "</TD>";
                    for (int j = 0; j < SchClass.group[i].PupilResult.Length; j++)
                    {
                        temp += "<TD>" + SchClass.group[i].StudyBall[j].ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Place.ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Bonus + "</TD>";
                    }
                    temp += "<TD>" + SchClass.group[i].ClassBonus.ToString() + "</TD>" +
                           "<TD>" + SchClass.group[i].ClassPlace.ToString() + "</TD>";
                    temp = temp + "</TR>";
                    builder.AppendLine(temp);
                }
                builder.Append("</TABLE>" +
                               "</BR><CODE>code by jcorp.ru</CODE>" +
                               "</BODY>" +
                               "</HTML>");
                #endregion
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка формирования отчёта.");
            }
            //save report
            try
            {
                if (File.Exists(file))
                    File.Delete(file);
                FileStream stream = new FileStream(file, FileMode.Create);
                StreamWriter writer = new StreamWriter(stream);
                writer.Write(builder.ToString());
                writer.Close();
                stream.Close();
                /*HTMLReport report = new HTMLReport(SchClass.ClassTitle, file);
                report.MdiParent = parent;
                report.Show();*/
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка сохранения файла.");
            }

        }

        /// <summary>
        /// Получение данных об учениках из таблицы
        /// </summary>
        /// <param name="dgv"></param>
        /// <returns></returns>
        public static SchoolClass FromDataGrid(DataGridView dgv)
        {

            if (dgv.ColumnCount < 2)
            {
                MessageBox.Show("Малое кол-во столбцов в таблице учеников.", "Ошибка данных");
                return null;
            }

            Pupil[] result = new Pupil[0];
            double[] ball = null;
            Result[] pres = null;
            try
            {
                for (int i = 0; i < dgv.RowCount; i++)
                {
                    Array.Resize(ref result, result.Length + 1);
                    ball = new double[dgv.ColumnCount - 1];
                    pres = new Result[dgv.ColumnCount - 1];
                    for (int j = 0; j < ball.Length; j++)
                    {
                        ball[j] = Convert.ToDouble(dgv.Rows[i].Cells[j + 1].Value);
                        pres[j].Bonus = 0;
                        pres[j].Place = 0;
                    }
                    result[i] = new Pupil();
                    result[i].Name = dgv.Rows[i].Cells[0].Value.ToString();
                    result[i].StudyBall = ball;
                    result[i].PupilResult = pres;
                }
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка получения данных....");
            }

            SchoolClass SResult = new SchoolClass();
            SResult.ClassTitle = "Class";
            SResult.group = result;

            SResult.Study = new string[dgv.Columns.Count - 1];
            for (int i = 0; i < dgv.Columns.Count - 1; i++)
            {
                SResult.Study[i] = dgv.Columns[i + 1].HeaderText;
            }
            PreviewData = SResult;
            return SResult;
        }

        /// <summary>
        /// Сохранение данных
        /// </summary>
        /// <param name="file">Файл</param>
        /// <param name="Class">Класс рейтинга</param>
        public static void SaveData(string file, SchoolClass Class)
        {
            try
            {
                XmlDocument document = new XmlDocument();
                XmlNode root = document.CreateNode(XmlNodeType.Element, "data", null);
                XmlNode pupil = document.CreateNode(XmlNodeType.Element, "pupils", null);
                XmlNode study = document.CreateNode(XmlNodeType.Element, "study", null);
                XmlAttribute attribute = document.CreateAttribute("Title");
                attribute.Value = Class.ClassTitle;
                root.Attributes.Append(attribute);
                XmlNode current = null;
                XmlNode result = null;
                for (int i = 0; i < Class.group.Length; i++)
                {
                    current = document.CreateNode(XmlNodeType.Element, "people", null);
                    attribute = document.CreateAttribute("Name");
                    attribute.Value = Class.group[i].Name;
                    current.Attributes.Append(attribute);
                    attribute = document.CreateAttribute("Place");
                    attribute.Value = Class.group[i].ClassPlace.ToString();
                    current.Attributes.Append(attribute);
                    attribute = document.CreateAttribute("Ball");
                    attribute.Value = Class.group[i].ClassBonus.ToString();
                    current.Attributes.Append(attribute);
                    //save result
                    for (int j = 0; j < Class.group[i].PupilResult.Length; j++)
                    {
                        result = document.CreateNode(XmlNodeType.Element, "result", null);

                        attribute = document.CreateAttribute("Ball");
                        attribute.Value = Class.group[i].StudyBall[j].ToString();
                        result.Attributes.Append(attribute);
                        attribute = document.CreateAttribute("Place");
                        attribute.Value = Class.group[i].PupilResult[j].Place.ToString();
                        result.Attributes.Append(attribute);
                        attribute = document.CreateAttribute("Bonus");
                        attribute.Value = Class.group[i].PupilResult[j].Bonus.ToString();
                        result.Attributes.Append(attribute);
                        current.AppendChild(result);
                    }
                    pupil.AppendChild(current);
                }
                for (int s = 0; s < Class.Study.Length; s++)
                {
                    while (Class.Study[s].IndexOf(' ') >= 0)
                        Class.Study[s] = Class.Study[s].Replace(' ', '_');
                    current = document.CreateNode(XmlNodeType.Element, Class.Study[s], null);
                    study.AppendChild(current);
                }
                root.AppendChild(pupil);
                root.AppendChild(study);
                document.AppendChild(root);
                document.Save(file);
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка сохранения данных");
            }
        }

        /// <summary>
        /// Сохранение в XML
        /// </summary>
        /// <param name="Class">Класс</param>
        /// <returns>XML</returns>
        public static string SaveDataXML(SchoolClass Class)
        {
            string res = "";
            try
            {
                XmlDocument document = new XmlDocument();
                XmlNode root = document.CreateNode(XmlNodeType.Element, "data", null);
                XmlNode pupil = document.CreateNode(XmlNodeType.Element, "pupils", null);
                XmlNode study = document.CreateNode(XmlNodeType.Element, "study", null);
                XmlAttribute attribute = document.CreateAttribute("Title");
                attribute.Value = Class.ClassTitle;
                root.Attributes.Append(attribute);
                XmlNode current = null;
                XmlNode result = null;
                for (int i = 0; i < Class.group.Length; i++)
                {
                    current = document.CreateNode(XmlNodeType.Element, "people", null);
                    attribute = document.CreateAttribute("Name");
                    attribute.Value = Class.group[i].Name;
                    current.Attributes.Append(attribute);
                    attribute = document.CreateAttribute("Place");
                    attribute.Value = Class.group[i].ClassPlace.ToString();
                    current.Attributes.Append(attribute);
                    attribute = document.CreateAttribute("Ball");
                    attribute.Value = Class.group[i].ClassBonus.ToString();
                    current.Attributes.Append(attribute);
                    //save result
                    for (int j = 0; j < Class.group[i].PupilResult.Length; j++)
                    {
                        result = document.CreateNode(XmlNodeType.Element, "result", null);

                        attribute = document.CreateAttribute("Ball");
                        attribute.Value = Class.group[i].StudyBall[j].ToString();
                        result.Attributes.Append(attribute);
                        attribute = document.CreateAttribute("Place");
                        attribute.Value = Class.group[i].PupilResult[j].Place.ToString();
                        result.Attributes.Append(attribute);
                        attribute = document.CreateAttribute("Bonus");
                        attribute.Value = Class.group[i].PupilResult[j].Bonus.ToString();
                        result.Attributes.Append(attribute);
                        current.AppendChild(result);
                    }
                    pupil.AppendChild(current);
                }
                for (int s = 0; s < Class.Study.Length; s++)
                {
                    while (Class.Study[s].IndexOf(' ') >= 0)
                        Class.Study[s] = Class.Study[s].Replace(' ', '_');
                    current = document.CreateNode(XmlNodeType.Element, Class.Study[s], null);
                    study.AppendChild(current);
                }
                root.AppendChild(pupil);
                root.AppendChild(study);
                document.AppendChild(root);
                Stream x = new MemoryStream();
                document.Save(x);
                x.Seek(0, SeekOrigin.Begin);
                StreamReader reader = new StreamReader(x);
                res = reader.ReadToEnd();
                reader.Close();
                x.Close();
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка сохранения данных");
            }
            return res;
        }

        /// <summary>
        /// Чтение данных
        /// </summary>
        /// <param name="filename">Файл</param>
        /// <returns>Класс рейтинга</returns>
        public static SchoolClass ReadData(string filename)
        {
            SchoolClass result = new SchoolClass();
            try
            {
                XmlDocument document = new XmlDocument();
                document.Load(filename);
                result.ClassTitle = document.ChildNodes[0].Attributes[0].Value;
                XmlNode pupil = document.ChildNodes[0].ChildNodes[0];
                XmlNode study = document.ChildNodes[0].ChildNodes[1];
                result.Study = new string[study.ChildNodes.Count];
                result.group = new Pupil[pupil.ChildNodes.Count];
                for (int i = 0; i < pupil.ChildNodes.Count; i++)
                {
                    result.group[i] = new Pupil();
                    result.group[i].Name = pupil.ChildNodes[i].Attributes[0].Value;
                    result.group[i].ClassPlace = Convert.ToInt32(pupil.ChildNodes[i].Attributes[1].Value);
                    result.group[i].ClassBonus = Convert.ToDouble(pupil.ChildNodes[i].Attributes[2].Value);
                    result.group[i].PupilResult = new Result[pupil.ChildNodes[i].ChildNodes.Count];
                    result.group[i].StudyBall = new double[pupil.ChildNodes[i].ChildNodes.Count];
                    for (int j = 0; j < pupil.ChildNodes[i].ChildNodes.Count; j++)
                    {
                        XmlNode Xresult = pupil.ChildNodes[i].ChildNodes[j];
                        result.group[i].StudyBall[j] = Convert.ToDouble(Xresult.Attributes[0].Value);
                        result.group[i].PupilResult[j].Place = Convert.ToInt32(Xresult.Attributes[1].Value);
                        result.group[i].PupilResult[j].Bonus = Convert.ToDouble(Xresult.Attributes[2].Value);
                    }
                }
                for (int s = 0; s < study.ChildNodes.Count; s++)
                {
                    result.Study[s] = study.ChildNodes[s].Name;
                }
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка загрузки.");
            }
            PreviewData = result;
            return result;
        }

        /// <summary>
        /// Чтение данных XML
        /// </summary>
        /// <param name="filename">XML</param>
        /// <returns>Класс рейтинга</returns>
        public static SchoolClass ReadDataXML(string xml)
        {
            SchoolClass result = new SchoolClass();
            try
            {
                XmlDocument document = new XmlDocument();
                document.LoadXml(xml);
                result.ClassTitle = document.ChildNodes[0].Attributes[0].Value;
                XmlNode pupil = document.ChildNodes[0].ChildNodes[0];
                XmlNode study = document.ChildNodes[0].ChildNodes[1];
                result.Study = new string[study.ChildNodes.Count];
                result.group = new Pupil[pupil.ChildNodes.Count];
                for (int i = 0; i < pupil.ChildNodes.Count; i++)
                {
                    result.group[i] = new Pupil();
                    result.group[i].Name = pupil.ChildNodes[i].Attributes[0].Value;
                    result.group[i].ClassPlace = Convert.ToInt32(pupil.ChildNodes[i].Attributes[1].Value);
                    result.group[i].ClassBonus = Convert.ToDouble(pupil.ChildNodes[i].Attributes[2].Value);
                    result.group[i].PupilResult = new Result[pupil.ChildNodes[i].ChildNodes.Count];
                    result.group[i].StudyBall = new double[pupil.ChildNodes[i].ChildNodes.Count];
                    for (int j = 0; j < pupil.ChildNodes[i].ChildNodes.Count; j++)
                    {
                        XmlNode Xresult = pupil.ChildNodes[i].ChildNodes[j];
                        result.group[i].StudyBall[j] = Convert.ToDouble(Xresult.Attributes[0].Value);
                        result.group[i].PupilResult[j].Place = Convert.ToInt32(Xresult.Attributes[1].Value);
                        result.group[i].PupilResult[j].Bonus = Convert.ToDouble(Xresult.Attributes[2].Value);
                    }
                }
                for (int s = 0; s < study.ChildNodes.Count; s++)
                {
                    result.Study[s] = study.ChildNodes[s].Name;
                }
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка загрузки.");
            }
            PreviewData = result;
            return result;
        }

        /// <summary>
        /// Выгрузить данные в HTML форму
        /// </summary>
        /// <param name="browser">Окно браузера</param>
        /// <param name="SchClass">Класс рейтинга</param>
        public static void NewVisualReport(ref WebBrowser browser, SchoolClass SchClass)
        {
            StringBuilder builder = new StringBuilder();
            try
            {
                #region Gen Report
                builder.Append("<HTML>" +
                               "<HEAD><TITLE>" + SchClass.ClassTitle + "</TITLE></HEAD>" +
                               "<BODY>" +
                               "<Font color=green><H2>Отчёт</H2>" +
                               "<H3>" + SchClass.ClassTitle + "</H3>" +
                               "<H3>Дата: " + DateTime.Now.ToString() + "</H3></Font>" +
                               "<TABLE BORDER=1>"
                              );
                //create head of document
                string head = "<TR><TH ROWSPAN=2>Участник</TH>";
                string temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH COLSPAN=3>" + SchClass.Study[i] + "</TH>";
                }
                temp += "<TH ROWSPAN=2>Сумма</TH>" +
                        "<TH ROWSPAN=2>Место</TH>";
                head = head + temp + "</TR>";
                builder.Append(head);
                temp = "";
                for (int i = 0; i < SchClass.Study.Length; i++)
                {
                    temp += "<TH>Балл</TH><TH>Место</TH><TH>Бонус</TH>";
                }
                temp = "<TR>" + temp + "</TR>";
                builder.Append(temp);
                for (int i = 0; i < SchClass.group.Length; i++)
                {
                    temp = "<TR><TD>" + SchClass.group[i].Name + "</TD>";
                    for (int j = 0; j < SchClass.group[i].PupilResult.Length; j++)
                    {
                        temp += "<TD>" + SchClass.group[i].StudyBall[j].ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Place.ToString() + "</TD>" +
                                "<TD>" + SchClass.group[i].PupilResult[j].Bonus + "</TD>";
                    }
                    temp += "<TD>" + SchClass.group[i].ClassBonus.ToString() + "</TD>" +
                           "<TD>" + SchClass.group[i].ClassPlace.ToString() + "</TD>";
                    temp = temp + "</TR>";
                    builder.AppendLine(temp);
                }
                builder.Append("</TABLE>" +
                               "</BR><CODE>code by Jurassik</CODE>" +
                               "</BODY>" +
                               "</HTML>");
                #endregion
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message, "Ошибка формирования отчёта.");
            }
            browser.DocumentText = builder.ToString();
        }

        /// <summary>
        /// Подсчёт лучших
        /// </summary>
        /// <param name="schclass">Класс рейтинга</param>
        /// <param name="rich">Контейнер</param>
        /// <param name="count">Количество</param>
        public static void CompileBest(SchoolClass schclass, ref RichTextBox rich, int count)
        {
            int i = 0;
            int temp = 0;
            rich.Clear();
            rich.AppendText(schclass.ClassTitle + "\n");
            rich.AppendText(DateTime.Now.ToShortDateString() + "\n\n");
            while (i < schclass.group.Length)
            {
                if (schclass.group[i].ClassPlace <= count)
                {
                    if (temp == schclass.group[i].ClassPlace)
                        rich.AppendText("    " +
                                        schclass.group[i].Name + "   " + schclass.group[i].ClassBonus + "\n");
                    else
                        rich.AppendText(schclass.group[i].ClassPlace.ToString() + ". " +
                                        schclass.group[i].Name + "   " + schclass.group[i].ClassBonus + "\n");
                    temp = schclass.group[i].ClassPlace;
                }
                else
                {
                    break;
                }
                i++;
            }
            rich.AppendText("\nмаксимум:  " + schclass.group.Length * schclass.Study.Length);
        }

        /// <summary>
        /// Сортировка
        /// </summary>
        /// <param name="Sch"></param>
        public static void Sort(ref SchoolClass Sch)
        {
            Pupil Ptemp = null;
            bool Pchanged = true;
            while (Pchanged)
            {
                Pchanged = false;
                for (int i = 0; i < Sch.group.Length - 1; i++)
                {
                    if (Sch.group[i].ClassBonus < Sch.group[i + 1].ClassBonus)
                    {
                        Ptemp = Sch.group[i];
                        Sch.group[i] = Sch.group[i + 1];
                        Sch.group[i + 1] = Ptemp;
                        Pchanged = true;
                    }
                }
            }
            PreviewData = Sch;
        }
    }
}